package com.lyn.xls;

import android.util.Log;

import com.lyn.file.FileUtil;

import java.io.BufferedWriter;
import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStreamWriter;
import java.lang.reflect.Field;
import java.util.LinkedList;
import java.util.List;

import jxl.Cell;
import jxl.Sheet;
import jxl.Workbook;
import jxl.write.Label;
import jxl.write.WritableSheet;
import jxl.write.WritableWorkbook;
import jxl.write.WriteException;

/**
 * Xls
 *
 * @author longyn 2023/2/3
 * @version 1.0.0
 */
public class Xls {

    private static final String TAG = "Xls";

    /**
     * 打开Xls文件
     *
     * @param inputStream xls文件inputStream
     * @param tClass      生成实体类Class
     * @return 实体集合
     */
    public static <T> List<T> open(InputStream inputStream, Class<T> tClass) {
        return open(inputStream, tClass, 0, 0);
    }

    /**
     * 打开Xls文件
     *
     * @param inputStream xls文件inputStream
     * @param tClass      生成实体类Class
     * @param startRow    开始行
     * @param endRow      结束行
     * @return 实体集合
     */
    public static <T> List<T> open(InputStream inputStream, Class<T> tClass, int startRow, int endRow) {
        try {
            Workbook workbook = Workbook.getWorkbook(inputStream);
            Sheet sheet = workbook.getSheet(0);
            int columns = sheet.getColumns();
            if (endRow == 0) {
                startRow = 0;
                endRow = sheet.getRows();
            } else {
                if (endRow >= sheet.getRows()) {
                    endRow = sheet.getRows();
                }
            }
            List<T> tList = new LinkedList<>();
            for (int r = startRow; r < endRow; r++) {
                T t = tClass.newInstance();
                Field[] declaredFields = t.getClass().getDeclaredFields();
                for (int c = 0; c < columns; c++) {
                    Cell cell = sheet.getCell(c, r);
                    String contents = cell.getContents();
                    for (Field field : declaredFields) {
                        field.setAccessible(true);
                        Column column = field.getAnnotation(Column.class);
                        if (column == null) {
                            continue;
                        }
                        if (column.index() == c) {
                            field.set(t, contents);
                        }
                    }
                }
                tList.add(t);
            }
            return tList;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    /**
     * 创建 xls文件
     * @param path xls文件
     * @param tList 数据列表
     * @param tClass 实体类
     * @param <T> 实体类型
     */
    public static <T> void create(String path, List<T> tList, Class<T> tClass) {
        WritableWorkbook workbook = null;
        try {
            File file = new File(path);
            if (!file.exists()) {
                file.createNewFile();
            }
            workbook = Workbook.createWorkbook(file);
        } catch (Exception e) {
            e.printStackTrace();
        }
        if (workbook == null) {
            return;
        }
        WritableSheet sheet = workbook.createSheet("sheet1", 0);
        if (sheet == null) {
            return;
        }
        for (int i = 0; i < tList.size(); i++) {
            T t = tList.get(i);
            Class<?> aClass = t.getClass();
            Field[] fields = aClass.getDeclaredFields();
            for (Field field : fields) {
                field.setAccessible(true);
                Column column = field.getAnnotation(Column.class);
                if (column == null) {
                    continue;
                }
                if (i == 0) {
                    try {
                        sheet.addCell(new Label(column.index(), i, column.title()));
                    } catch (WriteException e) {
                        e.printStackTrace();
                    }
                    continue;
                }
                try {
                    sheet.addCell(new Label(column.index(), i, (String) field.get(t)));
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }
        try {
            workbook.write();
            workbook.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * xls文件转换成资源string.xml文件
     *
     * @param inputStream   xls文件输入流
     * @param stringXmlPath string.xml文件输出路径
     * @return true成功 false 失败
     */
    public static boolean toStringXml(InputStream inputStream, String stringXmlPath) {
        List<StringXmlInfo> stringXmlInfoList = open(inputStream, StringXmlInfo.class);
        if (stringXmlInfoList == null || stringXmlInfoList.isEmpty()) {
            return false;
        }
        StringBuilder sb = new StringBuilder();
        sb.append("<?xml version=\"1.0\" encoding=\"utf-8\"?>").append("\n");
        sb.append("<resources>");
        for (StringXmlInfo stringXmlInfo : stringXmlInfoList) {
            sb.append("<string name=\"")
                    .append(stringXmlInfo.getKey())
                    .append("\">")
                    .append(stringXmlInfo.getValue())
                    .append("</string>")
                    .append("\n");
        }
        sb.append("</resources>");
        try {
            File file = new File(stringXmlPath);
            if (!file.exists()) {
                boolean createNewFile = file.createNewFile();
                Log.d(TAG, "createNewFile:" + createNewFile);
            }
            FileOutputStream fileOutputStream = new FileOutputStream(file);
            BufferedWriter bufferedWriter = new BufferedWriter(new OutputStreamWriter(fileOutputStream));
            bufferedWriter.write(sb.toString());
            bufferedWriter.flush();
            bufferedWriter.close();
            return true;
        } catch (Throwable e) {
            e.printStackTrace();
        }
        return false;
    }
}
